package com.gaofans.vertx.boot.dbutils.mapper;

import com.gaofans.vertx.boot.dbutils.mapper.domain.ResultMapper;
import io.vertx.core.Vertx;
import io.vertx.core.file.FileSystem;
import io.vertx.core.json.JsonObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import reactor.core.publisher.Flux;

import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * mapper文件加载器
 * @author gaofans
 */
public class JsonMapperLoader {

    private Vertx vertx;

    private static final Logger LOG = LoggerFactory.getLogger(JsonMapperLoader.class);

    public JsonMapperLoader(Vertx vertx) {
        this.vertx = vertx;
    }

    /**
     * 加载指定目录下的mapper文件
     * @param dir 查询的目录
     * @return ResultMapper Flux流
     */
    public Flux<ResultMapper> loadMapper(String dir){
        return Flux.<ResultMapper>create(sink -> {
            FileSystem fileSystem = this.vertx.fileSystem();
            fileSystem.readDir(dir, res -> {
                if(res.succeeded()){
                    List<String> files = res.result();
                    if(files.size() == 0){
                        sink.complete();
                        return;
                    }
                    LOG.info("找到{}个mapper文件",files.size());
                    AtomicInteger count = new AtomicInteger(0);
                    for (String file : files) {
                        String suffix = file.substring(file.lastIndexOf(".") + 1);
                        if (suffix.toLowerCase().equals("json")){
                            fileSystem.readFile(file,event -> {
                                if(event.succeeded()){
                                    JsonObject json = new JsonObject(event.result());
                                    sink.next(json.mapTo(ResultMapper.class));
                                }else {
                                    sink.error(event.cause());
                                }
                                if(count.addAndGet(1) == files.size()){
                                    sink.complete();
                                }
                            });
                        }
                    }
                }else {
                    sink.error(res.cause());
                    sink.complete();
                }
            });
        }).doOnComplete(() -> {
            LOG.info("mapper文件处理完毕");
        }).replay();
    }

}
